﻿using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;

namespace NumberRecognition.Models
{
    [Serializable]
    public class Neuron
    {
        private float[] weights;
        private float a = 0.001F; //параметр наклодна сигмоидальной ф-и. Slope Parameter
        private float alpha = 0.5F;
        private float y;
        private float[] delta;

        public Neuron(int countOfWeight)
        {
            weights = new float[countOfWeight + 1]; //Учитываем порог
            delta = new float[countOfWeight + 1];
        }

        public float ActivationFunction(float[] x) //Функция активации
        {
            float u = 0;

            for (int i = 0; i < weights.Length; i++)
            {
                if (i == 0)
                {
                    u += weights[i];
                }
                else
                {
                    u += weights[i] * x[i - 1];
                }
            }

            return y = 1.0F / (float)(1.0F + (Math.Exp(-a * u)));
        }

        public float DerivativeFunction() //Производная
        {
            return a * y * (1.0F - y);
        }

        public void SetRandomWeights()
        {
            var rand = new Random();

            for (var i = 0; i < weights.Length; i++)
            {
                weights[i] = (float)rand.NextDouble();
            }
        }

        public float GetWeight(int i)
        {
            return weights[i];
        }

        public float GetOutput()
        {
            return y;
        }

        public void CorrectWeight(float learningSpeed, float localGradient, float y, int i)
        {
            //delta[i] = alpha * delta[i] + learningSpeed * localGradient * y;
            //weights[i] = weights[i] + delta[i];
            weights[i] = weights[i] + learningSpeed * localGradient * y;
        }
    }
}
